package Core;
/*
 *  TextInput version 0.5.2
 *  Author: Unknown & Van Tan Tai 2011
 *  input Text with Key or Touch devices
 */
import javax.microedition.lcdui.Graphics;

public class TextInput
{
	public static TextInput me = null;

    private final int MAX_TIME_TO_CONFIRM_KEY = 14;// milisec

    private final int CARET_HEIGHT = 2;
    private final int CARET_WIDTH = 6;
    private final int CARET_SHOWING_TIME = 5;

    private final int TEXT_GAP_X = 7;
    private final int MAX_SHOW_CARET_COUNER = 10;

    public static final int INPUT_TYPE_ANY = 0;
    public static final int INPUT_TYPE_NUMERIC = 1;
    public static final int INPUT_TYPE_PASSWORD = 2;

    private String[] print = null;
    private String[] printabc = { " 0", ".,?!\"1-()@/:*+<=>;_$%&", "abc2", "def3", "ghi4", "jkl5", "mno6", "pqrs7", "tuv8", "wxyz9" };
    private String[] printABC = { " 0", ".,?!\"1-()@/:*+<=>;_$%&", "ABC2", "DEF3", "GHI4", "JKL5", "MNO6", "PQRS7", "TUV8", "WXYZ9" };

    private String mode[] = {"abc","ABC","123"};
    private int iMode = 0;
    private int inputTypeBak = 0;
    
    private String text = "";
    private boolean isPassword = false;
    private String passwordText = "";
    private String paintedText = "";
    private int caretPos = 0;
    private int counter = 0;
    private int maxTextLenght = 255;
    private int offsetX = 0;
    private int lastKey = -1983;
    private int keyInActiveState = 0;
    private int indexOfActiveChar = 0;
    private int showCaretCounter = MAX_SHOW_CARET_COUNER;
    public int inputType = INPUT_TYPE_ANY;
    public boolean isTypeNumeric = false;
    public int height=0,width=0,x=0,y=0,color=0;
    public boolean isFocused=false;
	public boolean isqwerty = false;
    
    public void setBound(int x,int y,int width,int height,int color)
    {
    	this.x=x;
    	this.y=y;
    	this.width=width;
    	this.height=height;
    	this.color=color;
    }
    public void setFocus()
    {
    	isFocused=true;
    	me = this;
		if(VirtualKEY.ins != null)
			VirtualKEY.ins.changeMode(iMode);
    }

    public TextInput(String text, int maxLen, int inputType) {
    	if(inputType != INPUT_TYPE_NUMERIC)
    		print = printabc;
    	else iMode = 2;
    	isTypeNumeric = (iMode == 2);
        this.text = text;
        this.maxTextLenght = maxLen;
        inputTypeBak = inputType;
        this.inputType = inputType;
        if(inputType==INPUT_TYPE_PASSWORD){
	        inputTypeBak = INPUT_TYPE_ANY;
	        this.inputType = INPUT_TYPE_ANY;
        	isPassword = true;
        	setPasswordTest();
        	paintedText=passwordText;
        }
        caretPos=text.length();
        //isqwerty = GLives.isQwerty;
        //System.out.println("========> TextInput QWERTY : " + isqwerty);
    }

    public void clear()
    {
        if (caretPos > 0 && text.length() > 0)
        {
            text = text.substring(0, caretPos - 1)+ text.substring(caretPos, text.length());
            if(isPassword)
            	passwordText = passwordText.substring(0, caretPos - 1)+ passwordText.substring(caretPos, passwordText.length());
            caretPos--;
            setOffset();
        }
    }
    public void clearAll()
    {
    	text="";
    	caretPos=0;
    	lastKey=-43;
    }
    public void setOffset()
    {
        if (isPassword)
            paintedText = passwordText;
        else
            paintedText = text;
        
        int w = width - TEXT_GAP_X - GLives.ins.bmf_normal.stringWidth(mode[iMode]) - 7;
        int tw = GLives.ins.bmf_normal.stringWidth(paintedText);
        int cw = GLives.ins.bmf_normal.stringWidth(paintedText.substring(0, caretPos));
        
        if (offsetX < 0 && tw + offsetX < w)
            offsetX = w - tw;
        if (offsetX + cw <= 0){
            offsetX = -cw;
        }
        else if (offsetX + cw >= w)
            offsetX = w - cw;
        if (offsetX > 0)
            offsetX = 0;
    }

    public void keyPressedAscii(int keyCode) {
    	try{
	        if (text.length() < maxTextLenght) {
	            String ttext = text.substring(0, caretPos) + (char) keyCode;
	            if (caretPos < text.length())
	                ttext = ttext + text.substring(caretPos, text.length());
	            text = ttext;
	            caretPos++;
	            setPasswordTest();
	            setOffset();
	        }
    	}
        catch(Exception e){}
    }
    public void keyPressedAny(int keyCode)
    {
		if(caretPos == 0 && text.length() == maxTextLenght){
			lastKey = -43;
		}
		else
        if (keyCode == lastKey)
        {
            indexOfActiveChar = (indexOfActiveChar + 1) % print[keyCode - KEY.NUM0].length();
            String ttext = text.substring(0, caretPos - 1) + print[keyCode - KEY.NUM0].charAt(indexOfActiveChar);
            if (caretPos < text.length())
                ttext = ttext + text.substring(caretPos, text.length());
            text = ttext;
            keyInActiveState = MAX_TIME_TO_CONFIRM_KEY;
            setPasswordTest();
        }
        else
    	if (text.length() <= maxTextLenght)
    	{
            indexOfActiveChar = 0;
            String ttext = text.substring(0, caretPos - (text.length() == maxTextLenght? 1 : 0)) + print[keyCode - KEY.NUM0].charAt(indexOfActiveChar);
            if (caretPos < text.length())
                ttext = ttext + text.substring(caretPos, text.length());
            text = ttext;
            keyInActiveState = MAX_TIME_TO_CONFIRM_KEY;
            if ((caretPos < text.length() && text.length() < maxTextLenght) || (text.length() == maxTextLenght && caretPos == text.length()-1))
            	caretPos++;
            setPasswordTest();
            setOffset();
    	}
        lastKey = keyCode;
    }

    public void keyPressedNumeric(int keyCode)
    {
        if (text.length() <= maxTextLenght)
        {
            String ttext = text.substring(0, caretPos - (text.length() == maxTextLenght? 1 : 0)) + String.valueOf(keyCode - KEY.NUM0);
            if (caretPos < text.length())
                ttext = ttext + text.substring(caretPos, text.length());
            text = ttext;
            keyInActiveState = MAX_TIME_TO_CONFIRM_KEY;
            if ((caretPos < text.length() && text.length() < maxTextLenght) || (text.length() == maxTextLenght && caretPos == text.length()-1))
            	caretPos++;
            setPasswordTest();
            setOffset();
        }
    }
    
    public void ChangeMode(int inewMode){
    	inChangeMode(inewMode);
    	VirtualKEY.ins.changeMode(inewMode);
    }
    public void inChangeMode(int inewMode){
    	if(inewMode==0){ // abc
			inputType = inputTypeBak;
			print = printabc;
		} else if(inewMode == 1){ // ABC
			inputType = inputTypeBak;
			print = printABC;
		} else if(inewMode == 2){ //123
			if(inputType == INPUT_TYPE_ANY || isPassword){
				inputTypeBak = inputType;
				inputType = INPUT_TYPE_NUMERIC;
			}
		}
    	iMode = inewMode;
    }
    
    public void updateTouch(int x, int y){
    	if(paintedText == null) return;
    	if(x < this.x || x > this.x + width || y < this.y || y > this.y + height) return;
    	int wT = x - this.x - TEXT_GAP_X - offsetX;
    	int i = GLives.ins.bmf_normal.stringPosFix(paintedText, wT);
    	if(i < 0) caretPos = 0; else if(i >= paintedText.length()) caretPos = paintedText.length(); else caretPos = i;
    	setOffset();
    }
    
    public boolean updateKeyPressed(int keyCode){
    	System.out.println("TextInput Key="+keyCode); //debug
    	
    	// F U N C T I O N
    	if(keyCode == KEY.POUND){ // #
    		System.out.println("Mode="+mode[iMode]);
    		if(isTypeNumeric)
    			return true;
    		iMode++;
    		if(iMode >= mode.length) iMode= 0;
    		ChangeMode(iMode);
    		KEY.AsciiKeyPressed=0;
    		return true;
    	}
    	if(keyCode == KEY.STAR){ // *
    		KEY.AsciiKeyPressed=0;
    		return true;
    	}
    	
       	if(keyCode==KEY.INVALID_KEY && KEY.AsciiKeyPressed != 0){
    		isqwerty =true;
    	}
       	
    	// Q W E R T Y
    	if(isqwerty) {
            if (KEY.AsciiKeyPressed == '-') { // E1, blackberry 
                if (KEY.AsciiKeyPressed == lastKey && keyInActiveState < MAX_TIME_TO_CONFIRM_KEY) {
                    text = text.substring(0, caretPos - 1) + '_';
                    this.paintedText = text;
                    setPasswordTest();
                    setOffset();
                    lastKey = -1984;
                    return true;
                }
                lastKey = '-';
            }
            if (KEY.AsciiKeyPressed >= 32) {
            	if(isPassword)
            		keyInActiveState = MAX_TIME_TO_CONFIRM_KEY;
            	
            	if(inputType == INPUT_TYPE_NUMERIC){
            		if(inputType == INPUT_TYPE_NUMERIC){
            			if(KEY.AsciiKeyPressed >= '0' && KEY.AsciiKeyPressed <= '9'){
            				keyPressedAscii(KEY.AsciiKeyPressed);
            				KEY.AsciiKeyPressed=0;
            			}
            			return true;
            		}
            	}
            	if(iMode==0)
            		KEY.AsciiKeyPressed = (""+(char)KEY.AsciiKeyPressed).toLowerCase().charAt(0);
            	else if(iMode==1)
            		KEY.AsciiKeyPressed = (""+(char)KEY.AsciiKeyPressed).toUpperCase().charAt(0);
                keyPressedAscii(KEY.AsciiKeyPressed);
                KEY.AsciiKeyPressed = 0;
//                if(KEY.AsciiKeyPressed >= '0' && KEY.AsciiKeyPressed <= '9')
//                	return false;
                return true;
            }
        }
    	
    	// N U M B E R
    	if(isFocused==false) return false;
    	
        if (keyCode >= KEY.NUM0 && keyCode <= KEY.NUM9) {
            if (inputType == INPUT_TYPE_ANY){            	
            	keyPressedAny(keyCode);            	
            }
            else if (inputType == INPUT_TYPE_NUMERIC){
            	keyPressedNumeric(keyCode);            
            }
            return true;
        }
        else if(keyCode==KEY.FIRE || keyCode==KEY.LEFT_SOFTKEY) {
        	return false;
        }
        else if (keyCode == KEY.UP || keyCode == KEY.DOWN){
        	isFocused = false;
        	return false;
        }
        else {
            indexOfActiveChar = 0;
            lastKey = -43;
            if (keyCode == KEY.LEFT){
                if (caretPos > 0){
                    caretPos--;
                    setOffset();
                    showCaretCounter = MAX_SHOW_CARET_COUNER;
                }
                return true;
            }
            else if (keyCode == KEY.RIGHT){
                if (caretPos < text.length()){
                    caretPos++;
                    setOffset();
                    showCaretCounter = MAX_SHOW_CARET_COUNER;
                }
                return true;
            }
            else if (keyCode == KEY.CLEAR || keyCode == KEY.RIGHT_SOFTKEY){
                clear();
                return true;
            }
            else{
                lastKey = keyCode;
                return true;
            }
        }
    }
    
    public void paint(Graphics g)
    {    	
        if (isPassword) paintedText = passwordText;
        else paintedText = text;

//      if (isFocused) g.setColor(0xff0000);
//      else g.setColor(0x000000);
//    	g.drawRoundRect(x, y, width-1, height, 10, 10);  
//    	g.setColor(255, 255, 255);
//      g.fillRoundRect(x+1, y+1, width-2, height-2, 10,10);
// debug  
//        g.setColor(0xFF0000);
//        g.drawRect(x, y, width, height);
        
        GLives.ins.bmf_normal.drawString(g, mode[iMode], x + width - 5 - GLives.ins.bmf_normal.stringWidth(mode[iMode]), y + (height - GLives.ins.bmf_normal.getHeight()) / 2, 0, 0x999999);
        g.setClip(x+TEXT_GAP_X, y+2, width- 15 - GLives.ins.bmf_normal.stringWidth(mode[iMode]), height-2);
    	GLives.ins.bmf_normal.drawString(g, paintedText, x + TEXT_GAP_X + offsetX, y + (height - GLives.ins.bmf_normal.getHeight()) / 2, 0, color);
            
        /** dau nhap nhay de danh chu */
        if (isFocused && (keyInActiveState > 0 || showCaretCounter > 0 || (counter / CARET_SHOWING_TIME) % 2 == 0)){
            g.setColor(0x0000ff);
            g.fillRect(TEXT_GAP_X + offsetX + x + GLives.ins.bmf_normal.stringWidth(paintedText.substring(0, caretPos)), y + (height + GLives.ins.bmf_normal.getHeight())/ 2, CARET_WIDTH, CARET_HEIGHT);
        }
        g.setClip(0, 0, GLives.ScreenWidth, GLives.ScreenHeight);       
    }

    private void setPasswordTest()
    {
        if (isPassword)
        {
            passwordText = "";
            for (int i = 0; i < text.length(); i++)
                passwordText = passwordText + "*";
            if (keyInActiveState > 0 && caretPos > 0)
                passwordText = passwordText.substring(0, caretPos - 1) + text.charAt(caretPos - 1) + passwordText.substring(caretPos, passwordText.length());
        }
    }

    public void update()
    {
        counter++;
        if (keyInActiveState > 0)
        {
            keyInActiveState--;
            if (keyInActiveState == 0)
            {
                indexOfActiveChar = 0;
                lastKey = -43;
                setPasswordTest();
            }
        }
        if (showCaretCounter > 0)
            showCaretCounter--;
    }

    public String getText()
    {
        return text;
    }

    public void setText(String text)
    {
        this.text = text;
        if(isPassword){
        	setPasswordTest();
        	paintedText=passwordText;
        }
        caretPos=text.length();
    }
}